package com.hoki.zj.hrm.userdetails;

import com.alibaba.fastjson.JSON;
import com.hoki.zj.hrm.asserts.GlobalAssert;
import com.hoki.zj.hrm.domain.LoginUser;
import com.hoki.zj.hrm.domain.Permission;
import com.hoki.zj.hrm.mapper.LoginUserMapper;
import com.hoki.zj.hrm.mapper.PermissionMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Component;

import java.util.Collection;
import java.util.List;
import java.util.stream.Collectors;

@Component
public class MyUserDetailService implements UserDetailsService {

    @Autowired
    private LoginUserMapper loginUserMapper;
    
    @Autowired
    private PermissionMapper permissionMapper;
    
    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        // 1.判断参数
        GlobalAssert.hasText(username, "用户名为空!!");
        // 2.根据用户名查询数据库中的用户信息
        LoginUser loginUser = loginUserMapper.selectByUsername(username);
        // 3.是否查询到数据
        GlobalAssert.isNull(loginUser, "用户不存在!!");
        // 4.查询当前用户的权限
        List<Permission> permissions = permissionMapper.selectByUserId(loginUser.getId());
        // 5.将权限列表转换为SimpleGrantedAuthority类型的集合
        Collection<SimpleGrantedAuthority> authorities =
                permissions.stream().map(MyUserDetailService :: apply).collect(Collectors.toList());
        // 获取loginUser中的密码
        String password = loginUser.getPassword();
        loginUser.setPassword(""); // 清空密码
        // 6.将loginUser转为json字符串
        String loginUserStr = JSON.toJSONString(loginUser);
        // 7.返回UserDetails(封装loginUser, 密码, 权限列表)
        return new User(loginUserStr, password, authorities);
    }
    
    // toSimpleGrantedAuthority
    private static SimpleGrantedAuthority apply(Permission permission) {
        return new SimpleGrantedAuthority(permission.getSn());
    }
}
